package com.marco;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * IPUtils.java
 * Create on 2017/3/22
 * Copyright(c) JD Inc 2017. All Rights Reserved.
 * <pre>
 * 功能说明：封装IP相关的方法
 * </pre>
 */
public class IPUtils {
    /**
     * 根据给定IP校验是否属于IPv4格式
     */
    public static boolean isIpv4(String ipAddress) {
        String ip = "^(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\."
                + "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\."
                + "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\."
                + "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)$";
        Pattern pattern = Pattern.compile(ip);
        Matcher matcher = pattern.matcher(ipAddress);
        return matcher.matches();
    }

    /**
     * 将IP转换成十进制数字
     */
    public static Long toDecimal(String ip) {
        try {
            String[] ss = ip.split("\\.");
            Long a, b, c, d;
            a = Long.parseLong(ss[0]);
            b = Long.parseLong(ss[1]);
            c = Long.parseLong(ss[2]);
            d = Long.parseLong(ss[3]);
            return (a << 24) | (b << 16) | (c << 8) | d;
        } catch (Exception e) {
            return null;
        }
    }

    /**
     * 将十进制的IP数字转换成可读的标准IP格式
     */
    public static String toIP(long l) {
        try {
            return Long.toString(l >> 24) + "." + Long.toString((l >> 16) & 255) + "."
                    + Long.toString((l >> 8) & 255) + "." + Long.toString(l & 255);
        } catch (Exception e) {
            return null;
        }
    }

    /**
     * 将IP段分割成IP，保留前三段
     */
    public static List<String> listIPWithThreeSeg(String ipMin, String ipMax) {
        List<String> rs = new ArrayList<String>();
        Set<String> sets = new HashSet<>();
        long ipMinDecimal = toDecimal(ipMin);
        long ipMaxDecimal = toDecimal(ipMax);
        for (long i = ipMinDecimal; i <= ipMaxDecimal; i++) {
            sets.add(toIP((i/256)*256));
        }
        rs.addAll(sets);
        return rs;
    }
}
